#include<string.h>
#include<stdlib.h>
#include<stdio.h>

#include"linklist.h"

static int __is_empty(const list *mylist);
static int __always_cmp_ture(const void *data1, const void *data2);
//初始化
int list_init(list ** mylist, const int size){
	*mylist = malloc(sizeof(list));
	if(NULL == *mylist){
		return -1;
	}
	(*mylist)->head.next = &(*mylist)->head;
	(*mylist)->head.data = NULL;

	(*mylist)->size = size;

	return 0;
}
//增

static node_t  *__creat_node(const void *data1, int size){
	node_t *p = malloc(sizeof(node_t));
	if(NULL == p)
		return NULL;
	p->data = malloc(size);
	if(NULL == p->data){
		free(p);
		p = NULL;
		return NULL;
	}
	memcpy(p->data, data1, size);
	p->next = NULL;

	return p;
}

int list_insert(list *mylist, const void *data1){
	node_t *node = NULL;

	node = __creat_node(data1, mylist->size);
	if(NULL == node)
		return -1;

	node->next = mylist->head.next;
	mylist->head.next = node;

	return 0;
}


int list_insert_tail(list *mylist, const void *data1){
	node_t *cur = NULL;

	node_t *node = NULL;
	node = __creat_node(data1, mylist->size);
	if(NULL == node)
		return -1;
	if(__is_empty(mylist)){
		mylist->head.next = node;
		node->next = &(mylist->head);
		return 0;
	}
	for(cur = mylist->head.next; cur->next != &(mylist->head); cur = cur->next);
	cur->next = node;
	node->next = &(mylist->head);

	return 0;
}

static node_t *__find_pre(const list *mylist, const void *data, cmp_t cmp){
	if(__is_empty(mylist))
		return NULL;

	node_t *pre = (node_t *)&mylist->head;
	node_t *cur = pre->next;

	while(cur != &mylist->head){
		if(cmp(cur->data, data) == 0){
			return pre;
		}
		pre = cur;
		cur = cur->next;
	}
	return NULL;
}
//查
void * list_search(const list *mylist, const void *data1, cmp_t cmp){
	node_t *pre = __find_pre(mylist, data1, cmp);
	node_t *cur;
	if(pre == NULL){
		return NULL;
	}
	cur = pre->next;

	return cur;
}
//删
int list_delete(list *mylist, const void *data1, cmp_t cmp){
	node_t *pre = __find_pre(mylist, data1, cmp);
	node_t *cur;
	if(pre == NULL)
		return -1;
	cur = pre->next;
	
	pre->next = cur->next;
	cur->next = NULL;
	free(cur->data);
	cur->data = NULL;
	free(cur);
	cur = NULL;
	
	return 0;
}
//改
int list_updata(const list *mylist, const void *data1, const void *data2, cmp_t cmp){
	node_t *pre = __find_pre(mylist, data1, cmp);
	node_t *cur;
	if(pre != NULL){
		cur = pre->next;
		memcpy(cur->data, data2, mylist->size);
		return 0;
	}
	return -1;
}
//展示
int list_display(const list *mylist, pri_t pri){
	node_t *p = mylist->head.next;
	if(&(mylist->head) == p)
		return -1;
	for(;p != &mylist->head; p = p->next){
		pri(p->data);
	}
	return 0;
}
static int __always_cmp_ture(const void *data1, const void *data2){
	return 0;
}
//销毁
void list_destroy(list **mylist){
	if(__is_empty(*mylist)){
		return;
	}
	while(!__is_empty(*mylist)){
		list_delete(*mylist, NULL,__always_cmp_ture);
	}

	free(*mylist);
	*mylist = NULL;
}


static int __is_empty(const list *mylist){
	return mylist->head.next == &(mylist->head);
}



int list_reverse(list *mylist){
	if(__is_empty(mylist))
		return -1;
	node_t *cur = mylist->head.next;
	node_t *fetch;
	while(cur->next != &(mylist->head)){
		fetch = cur->next;
		cur->next = fetch->next;
		fetch->next = mylist->head.next;
		mylist->head.next = fetch;
	}
	return 0;
}
